﻿using System;
using System.Collections.Generic;
using System.Linq;
using Autodesk.Revit.DB;
using StairsModuleAndEdit.StairsModel.CommonUnit;

namespace StairsModuleAndEdit.HYElevator.Kit
{
	internal class CalHostForEachLayer
	{
		public CalHostForEachLayer(Autodesk.Revit.DB.Document doc, XYZ pt1, XYZ pt2, Dictionary<ViewPlan, bool> FloorLevels)
		{
			this.m_doc = doc;
			this.spt = pt1;
			this.ept = pt2;
			this.m_FloorLevels = FloorLevels;
			this.m_FloorPlan = (from l in this.m_FloorLevels
			select l.Key).ToList<ViewPlan>();
		}

		public Dictionary<ElementId, ElementId> Execute()
		{
			Dictionary<ElementId, ElementId> dictionary = new Dictionary<ElementId, ElementId>();
			try
			{
				FilterWallByEachLayer instance = FilterWallByEachLayer.GetInstance(this.m_doc, this.m_FloorPlan);
				foreach (KeyValuePair<ViewPlan, bool> keyValuePair in this.m_FloorLevels)
				{
					ViewPlan key = keyValuePair.Key;
					List<WallLocation> list = instance.DicWallEachLayer[key.GenLevel.Id];
					double elevation = key.GenLevel.Elevation;
					XYZ xyz = new XYZ(this.spt.X, this.spt.Y, elevation);
					XYZ xyz2 = new XYZ(this.ept.X, this.ept.Y, elevation);
					Line line = Line.CreateBound(xyz, xyz2);
					XYZ xyz3 = line.Evaluate(0.1, true);
					XYZ xyz4 = line.Evaluate(0.9, true);
					line = Line.CreateBound(xyz3, xyz4);
					foreach (WallLocation wallLocation in list)
					{
						Wall wall = this.m_doc.GetElement(wallLocation.WallId) as Wall;
						double offestValue = wall.Width + 0.2;
						bool flag = Geometry.IsCurvCrossCurve(line, wallLocation.curve, offestValue);
						if (flag)
						{
							dictionary.Add(key.GenLevel.Id, wallLocation.WallId);
							break;
						}
					}
				}
			}
			catch (Exception)
			{
				return null;
			}
			return dictionary;
		}

		public static Face GetFaceByNoraml(Element elem, XYZ noraml, View view)
		{
			Face result = null;
			IList<Solid> source = new List<Solid>();
			CalHostForEachLayer.GetExtrusionGeo(elem, ref source, view);
			FaceArray faces = source.First<Solid>().Faces;
			double num = Math.PI*2;
			foreach (object obj in faces)
			{
				Face face = (Face)obj;
				double num2 = noraml.AngleTo(face.ComputeNormal(UV.Zero));
				if (num2 < num)
				{
					num = num2;
					result = face;
				}
			}
			return result;
		}

		private static bool GetExtrusionGeo(Element elem, ref IList<Solid> Solids, View view)
		{
			GeometryElement elem2 = elem.get_Geometry(new Options
			{
				ComputeReferences = true,
				IncludeNonVisibleObjects = true,
				View = view
			});
			return CalHostForEachLayer.GetElemSolid(elem2, ref Solids);
		}

		private static bool GetElemSolid(GeometryElement elem, ref IList<Solid> Solids)
		{
			foreach (GeometryObject geometryObject in elem)
			{
				if (geometryObject is Solid)
				{
					Solid item = geometryObject as Solid;
					Solids.Add(item);
				}
				else if (geometryObject is GeometryInstance)
				{
					GeometryInstance geometryInstance = geometryObject as GeometryInstance;
					GeometryElement symbolGeometry = geometryInstance.GetSymbolGeometry();
					bool elemSolid = CalHostForEachLayer.GetElemSolid(symbolGeometry, ref Solids);
					if (!elemSolid)
					{
						return elemSolid;
					}
				}
			}
			return true;
		}

		private Document m_doc;

		private XYZ spt;

		private XYZ ept;

		private Dictionary<ViewPlan, bool> m_FloorLevels;

		private List<ViewPlan> m_FloorPlan;
	}
}
